package copyengine.utils
{

	/**
	 *Use one uint to record 32 attribute
	 */
	public class UintAttribute
	{
		public static function setAttribute(_val:uint, _index:int):uint
		{
			if (!hasAttribute(_val, _index))
			{
				_val|=(1 << _index);
			}
			return _val;
		}

		public static function removeAttribute(_val:uint, _index:int):uint
		{
			if (hasAttribute(_val, _index))
			{
				_val&=~(1 << _index);
			}
			return _val;
		}

		public static function hasAttribute(_val:uint, _index:int):Boolean
		{
			return (_val & (1 << _index)) != 0;
		}

		public static function cleanValueExceptMask(_val:uint, _mask:uint):uint
		{
			return _val & _mask;
		}

		/**
		 *根据给定的mask找到对应的值
		 * ex:
		 * mask : 0000,1111,0000
		 * value: 0000,1000,0000
		 * 返回的值: 1000
		 */
		public static function getValueByMask(_val:uint, _mask:uint):uint
		{
			var maskCount:uint=maskSize(_mask);
			var offsetCount:uint=maskOffset(_mask);
			_val&=_mask;
			_val>>>=offsetCount;
			return _val;
		}

		/**
		 * 将对应的值设置在mask的位置上
		 * ex:
		 * mask:0000,1111,0000
		 * value:1000,1000,1000
		 * setValue:0011
		 * 结果1000,0011,0000（对应mask位置上的值会覆盖原来的值）
		 */
		public static function setValueByMask(_val:uint, _setValue:uint, _mask:uint):uint
		{
			var offsetCount:uint=maskOffset(_mask);
			//将设置的value向左偏移mask的位数
			//如mask offset了5位,value的值是 00101
			//则偏移后变为 00101,00000
			_setValue<<=offsetCount;
			//将vlaue对应mask位置的值清除
			_val&=(~_mask);
			//将setValue的值 或 val 就是把value的值写到val中，因为val相应mask地方为0
			//并且setValue非mask地方也为0
			_val|=_setValue;
			return _val;
		}

		/**
		 *取得mask的位数
		 * ex:
		 * mask : 0000,1111,1100
		 * 返回6
		 */
		private static function maskSize(_mask:uint):uint
		{
			var size:uint=0;
			//一个uint是32位，遍历所有32位 计算一共有多少个1
			//注意::mask一定是要连续的
			for (var i:int=0; i < 32; i++)
			{
				if (hasAttribute(_mask, i))
				{
					size++;
				}
			}
			return size;
		}

		/**
		 *计算Mask的偏移值
		 * ex:
		 *  mask = 0011,1110,0000 掩码位数是5位
		 * 则用maks与11111（5个1）去比较 得出mask偏移多少位
		 *
		 */
		private static function maskOffset(_mask:uint):uint
		{
			var offset:uint=0;
			for (var i:int=0; i < 32; i++)
			{
				if (!hasAttribute(_mask, i))
				{
					offset++;
				}
				else
				{
					return offset;
				}
			}
			return offset;
		}

	}
}
